home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
FM Towns: Free Software Collection 6
/
FM Towns Free Software Collection 6.iso
/
t_os
/
chtiff
/
source
/
chtiff5.c
< prev
next >
Wrap
Text File
|
1993-07-08
|
10KB
|
378 lines
/*
ファイル名指定を良くするために、DOS専用関数 _splitpath を使用してます。
MS-C のみに通用する関数かもしれませんので、代用として、__splitpath を用意
してます。信頼度は_splitpath の方が上でしょう。
*/
#include<stdio.h>
#include<stdlib.h>
#include<ctype.h>
#include<string.h>
#include"define.h"
#define MAIN 1
#include"function.h"
/* グローバル変数の宣言 */
TIFF_INFO from,to;
int kill_to;
void __splitpath(char *string, char *drive, char *dir, char *fname, char *ext)
{
char *p;
int i;
*drive = *dir = *fname = *ext = 0;
if( isalpha(*string) && (*(string+1)==':') ){
*drive = *string;
*(drive+1) = ':';
*(drive+2) = 0;
string += 2;
}
else *drive = 0;
*dir = 0;
while(1){
for( p = string; *p && (*p != '\\'); p++);
if( *p == 0 ) break;
while( string != p ){
*dir = *string;
dir++;
string++;
}
*dir = *string;
dir++;
string++;
}
*dir = 0;
for( p = string; *p && (*p != '.'); p++);
if( *p == 0 ){ /* 拡張子なし */
strcpy( fname, string );
*ext = 0;
}
else{ /* 拡張子あり */
while( string != p ){
*fname = *string;
fname++;
string++;
}
*fname = 0;
/* 拡張子書き込み。a.b.c という記述にも対応するため、カウントしている */
for(i=0; i<4; i++){
if( *string == 0 ) break;
*ext = *string;
ext++;
string++;
}
*ext = 0;
}
}
main(int argc, char *argv[])
{
unsigned long offset;
int i, j, from_file, to_file, del, Intel, stop, expand;
char string[2][256];
char drive[2][3];
char dir[2][256];
char fname[2][9];
char ext[2][5];
char ren[256];
from_file = to_file = 0;
expand = 0;
kill_to = 0;
to.Compression = 1;
del = 0;
stop = 1;
Intel = 2;
to.Bits_Per_Sample = 0;
to.Rows_Per_Strip = 0;
ren[0] = 0;
string[0][0] = string[1][0] = 0;
for(i=1; i<argc; i++){
if( (*argv[i]=='/')||(*argv[i]=='-') ) goto OPTION;
if( from_file == 0 ){ from_file = i; continue;}
if( to_file == 0 ) to_file = i;
continue; /* 2つ以上のファイル指定は無視 */
OPTION:
switch( *(argv[i]+1) ){
case'c': case'C':
to.Compression = 5;
continue;
case'd': case'D':
switch( *(argv[i]+2) ){
case'x': case'X':
to.X_Resolution.bunsi = atol( argv[i]+3 );
continue;
case'y': case'Y':
to.Y_Resolution.bunsi = atol( argv[i]+3 );
continue;
default:
to.X_Resolution.bunsi = to.Y_Resolution.bunsi =
atol( argv[i]+2 );
}
continue;
case'b': case'B':
j = atoi( argv[i]+2 );
if( ( j%8 )||( j<8 )||( 24<j) ){
printf("この変換には対応してません。%d",j);
usage();
exit(1);
}
to.Bits_Per_Sample = j;
continue;
case'i': case'I':
Intel = 1;
continue;
case'm': case'M':
Intel = 0;
continue;
case's': case'S':
j = atoi( argv[i]+2 );
if(j<=0){
puts("Sオプション指定が間違ってます。");
usage();
exit(1);
}
to.Rows_Per_Strip = j;
continue;
case'n': case'N':
stop = 0;
continue;
case'e': case'E':
expand = 1;
continue;
default:
usage();
exit(0);
}
}
/* 拡張子省略・ファイル名設定なしなどに対応する。*/
if( from_file == 0 ){
fputs("変換元ファイル名が、指定されてません\n",stderr);
usage();
exit(1);
}
strcpy(string[0],argv[from_file]);
__splitpath(string[0], drive[0], dir[0], fname[0], ext[0]);
if( *fname[0] == 0 ){
fputs("変換元ファイル名が、指定されてません\n",stderr);
usage();
exit(1);
}
if( *ext[0] == 0 ) strcat(string[0],".tif");
/* 拡張子省略・変換先設定なしなどに対応 */
if( to_file == 0 ){
sprintf(string[1],".\\%s.@",fname[0]); /* 同名をカレントに作成 */
ext[1][0] = 0;
}
else{
strcpy( string[1], argv[ to_file ] );
__splitpath(string[1], drive[1], dir[1], fname[1], ext[1]);
if( *fname[1] == 0 ){
if( (drive[1]==0) && (dir[1]==0) ){
fputs("変換先ファイル名が、指定されてません\n",stderr);
usage();
exit(1);
}
sprintf(string[1],"%s%s%s.@",drive[1],dir[1],fname[0]);
strcpy(ext[1],".tif");
}
else{
sprintf(string[1],"%s%s%s.@",drive[1],dir[1],fname[1]);
}
}
if( *ext[1] == 0 ) strcpy( ext[1], ".tif" );
if( NULL==(from.fp=fopen(string[0],"rb")) ){
fprintf(stderr,"変換元 %s が見つかりません。\n",string[0]);
usage();
exit(1);
}
if( isIntel() == -1 ){
fprintf(stderr,"%sは TIFF file ではないようです。",argv[from_file]);
exit(1);
};
offset = read_LONG(0L);
fseek(from.fp, offset, SEEK_SET);
read_IFD();
if(from.Intel) puts("Intel形式です。");
else puts("モトローラ形式です。");
printf("%8lu : New Subfile Type\n",from.New_Subfile_Type);
printf("%8u : Image Width\n",from.Image_Width);
printf("%8u : Image Length\n",from.Image_Length);
printf("%8u : Bits Per Pixel",from.Bits_Per_Sample);
if(from.Opacity) puts("(with opacity)"); else puts("");
printf("%8u : Compression\n",from.Compression);
printf("%8u : Photo Interp\n",from.Photo_Interp);
printf("%8u : Fill order\n",from.Fill_Order);
if( from.Strip_Offset == NULL )
puts("-------- : Strip_Offset");
else
printf("%08lx : Strip Offset\n",*from.Strip_Offset);
printf("%8u : Samples Per Pixel\n",from.Samples_Per_Pixel);
printf("%8lu : Rows Per Strip\n",from.Rows_Per_Strip);
if( from.Strips_ByteCount == NULL )
puts("-------- : Strips ByteCount");
else
printf("%8lu : Strips ByteCount\n",*from.Strips_ByteCount);
printf("%8u : Max Sample Value\n",from.Max_Sample_Value);
printf("%4lu/%4lu: X Resolution\n",from.X_Resolution.bunsi,from.X_Resolution.bunbo);
printf("%4lu/%4lu: Y Resolution\n",from.Y_Resolution.bunsi,from.Y_Resolution.bunbo);
printf("%8u : Planer Config\n",from.Planer_Config);
printf("%8d : Color Map\n",from.Color_Map);
/* for(i=0; i<from.Strips; i++)
printf("Strip %d: offset %08lx length %08x\n",
i,*(from.Strip_Offset+i),*(from.Strips_ByteCount+i) ); */
/* 今のところ、JPEG等には非対応 */
if( ( from.Compression != 1 ) && ( from.Compression !=5 ) ){
fputs("LZW圧縮以外の圧縮には、対応してません。\n",stderr);
exit(1);
};
/* 書き込みファイルの属性決定 */
if( Intel == 2 ) to.Intel = from.Intel;
else to.Intel = Intel;
to.Opacity = 0;
to.Strips = 0;
to.New_Subfile_Type = 0;
to.Image_Width = from.Image_Width;
if(expand) to.Image_Width += from.Image_Width / 3;
to.Image_Length = from.Image_Length;
if(to.Bits_Per_Sample == 0) to.Bits_Per_Sample = from.Bits_Per_Sample;
switch(to.Bits_Per_Sample){
case 8:
to.Photo_Interp = 3;
to.Samples_Per_Pixel = 1;
break;
case 16:
to.Photo_Interp = 1;
to.Samples_Per_Pixel = 1;
break;
case 24:
to.Photo_Interp = 2;
to.Samples_Per_Pixel = 3;
}
to.Fill_Order = 1;
if( to.Bits_Per_Sample == 16 )
to.Max_Sample_Value = (1<<15)-1;
else
to.Max_Sample_Value = (1<<to.Bits_Per_Sample)-1;
/* 解像度のチェックをしないと、NeXTなどで誤動作をまねきます */
if( to.X_Resolution.bunsi == 0 || to.X_Resolution.bunbo == 0 )
if( from.X_Resolution.bunsi && from.X_Resolution.bunbo ){
to.X_Resolution.bunsi = from.X_Resolution.bunsi;
to.X_Resolution.bunbo = from.X_Resolution.bunbo;
}
else{
to.X_Resolution.bunsi = 72UL;
to.X_Resolution.bunbo = 1UL;
}
if( to.Y_Resolution.bunsi == 0 || to.Y_Resolution.bunbo == 0 )
if( from.Y_Resolution.bunsi && from.Y_Resolution.bunbo ){
to.Y_Resolution.bunsi = from.Y_Resolution.bunsi;
to.Y_Resolution.bunbo = from.Y_Resolution.bunbo;
}
else{
to.Y_Resolution.bunsi = 72UL;
to.Y_Resolution.bunbo = 1UL;
}
to.Planer_Config = 1;
to.Color_Map = 0;
if( to.Rows_Per_Strip == 0 )
/* Townsの16ビットはストライプ分割を認めない、意固地だそうな */
if( ( to.Compression==1)||( to.Bits_Per_Sample == 16 ) )
to.Rows_Per_Strip = to.Image_Length;
else
to.Rows_Per_Strip = (TEMP_SIZE)/(to.Image_Width*to.Bits_Per_Sample/8L);
j = (to.Image_Length / to.Rows_Per_Strip) + 1;
to.Strips_ByteCount=MALLOC( 4UL*j );
to.Strip_Offset=MALLOC( 4UL*j );
printf("\n[ %s ] → [ %s ] の変換です。\n",string[0],string[1]);
puts("変換先のファイルの書式は");
if( to.Compression == 5 ) fputs("LZW圧縮/",stdout);
printf("%dビット/1ストライプ %d ライン/",to.Bits_Per_Sample, to.Rows_Per_Strip);
if(expand) fputs("幅拡張/",stdout);
if(to.Intel == 0 ) puts("モトローラ式");
else puts("インテル式");
if( stop ){
puts("です。リターンで開始します。");
fgetc(stdin);
}
else puts("です。");
if( NULL == (to.fp = fopen(string[1],"wb")) ){
fprintf(stderr,"ファイル %s の作成に失敗しました。\n",string[1]);
exit(1);
};
if(to.Intel) write_SHORT(0UL,0x4949); /* intel形式 */
else write_SHORT(0UL,0x4d4d); /* モトローラ形式 */
write_SHORT(0UL,42); /* バージョン */
write_LONG(0UL,0UL); /* IFD offset のダミー値 */
/* さて、グラフィックデータの書き込みっと・・・ */
switch(from.Bits_Per_Sample){
case 8 : change8(expand) ; break;
case 12: change12(expand); break;
case 16: change16(expand); break;
case 24: change24(expand); break;
case 32: change32(expand); break;
default: fputs("この変換には対応してません。\n",stderr);
exit(1);
};
/* 残るはIFDだ! */
puts("IFD を書き込みます。");
write_IFD();
puts("変換は終了しました。");
fclose(to.fp);
__splitpath( string[1], drive[1], dir[1], fname[1], ext[0]);
*ren = 0;
sprintf(ren,"%s%s%s%s",drive[1],dir[1],fname[1],ext[1]);
if( NULL == fopen( ren,"rb") ) rename(string[1],ren);
else printf("Rename できなかったので、[ %s ]のまま残します。\n",string[1]);
}